<template>
  <div class="h-screen flex flex-col bg-gray-50" :class="{ 'fullscreen-mode': isFullscreen }">
    <!-- 顶部工具栏 -->
    <header class="bg-white border-b border-gray-200 px-6 py-4 flex-shrink-0" v-show="!isFullscreen">
      <div class="flex items-center justify-between">
        <div class="flex items-center space-x-4">
          <h1 class="text-2xl font-bold text-gray-800 flex items-center">
            <i class="fas fa-project-diagram text-blue-500 mr-3"></i>
            ER 图编辑器 (Mermaid + DBML)
          </h1>
          <div class="text-sm text-gray-500">
            基于 Mermaid.js 和 DBML 的专业数据库设计工具
          </div>
        </div>

        <div class="flex items-center space-x-3">
          <!-- 模板选择 -->
          <select 
            v-model="selectedTemplate"
            @change="loadTemplate"
            class="px-3 py-2 text-sm border border-gray-300 rounded-lg focus:outline-none focus:ring-2 focus:ring-blue-500 transition-colors"
          >
            <option value="">选择模板</option>
            <option value="ecommerce">电商系统</option>
            <option value="blog">博客系统</option>
            <option value="crm">CRM系统</option>
          </select>
          
          <!-- 布局方向 -->
          <select 
            v-model="diagramDirection"
            @change="updateDiagram"
            class="px-3 py-2 text-sm border border-gray-300 rounded-lg focus:outline-none focus:ring-2 focus:ring-blue-500 transition-colors"
          >
            <option value="TB">上下布局</option>
            <option value="LR">左右布局</option>
          </select>
          
          <!-- 操作按钮 -->
          <button
            @click="formatMarkdown"
            class="px-4 py-2 text-sm bg-purple-500 text-white rounded-lg hover:bg-purple-600 transition-colors shadow-sm"
          >
            <i class="fas fa-magic mr-2"></i>
            格式化
          </button>
          
          <button
            @click="generateSQL"
            class="px-4 py-2 text-sm bg-green-500 text-white rounded-lg hover:bg-green-600 transition-colors shadow-sm"
          >
            <i class="fas fa-database mr-2"></i>
            生成 SQL
          </button>
        
          <button
            @click="exportDiagram"
            class="px-4 py-2 text-sm bg-blue-500 text-white rounded-lg hover:bg-blue-600 transition-colors shadow-sm"
          >
            <i class="fas fa-download mr-2"></i>
            导出
          </button>

          <!-- 全屏切换 -->
          <button
            @click="toggleFullscreen"
            class="px-4 py-2 text-sm bg-indigo-500 text-white rounded-lg hover:bg-indigo-600 transition-colors shadow-sm"
            :title="isFullscreen ? '退出全屏' : '进入全屏'"
          >
            <i :class="isFullscreen ? 'fas fa-compress' : 'fas fa-expand'" class="mr-2"></i>
            {{ isFullscreen ? '退出全屏' : '全屏' }}
          </button>
        </div>
      </div>
    </header>

    <!-- 主工作区 -->
    <div class="flex-1 flex min-h-0 relative">
      <!-- 左侧代码编辑器 -->
      <div 
        class="bg-white border-r border-gray-200 flex flex-col transition-all duration-300 ease-in-out"
        :style="{ width: leftPanelWidth + 'px', minWidth: '300px', maxWidth: '70%' }"
      >
        <div class="px-4 py-3 bg-gray-50 border-b border-gray-200 flex-shrink-0">
          <div class="flex items-center justify-between">
            <h3 class="font-semibold text-gray-800 flex items-center">
              <i class="fas fa-code text-green-500 mr-2"></i>
              Markdown 定义
            </h3>
            <div class="flex items-center space-x-2 text-sm text-gray-500">
              <span>{{ markdownContent.length }} 字符</span>
              <button
                @click="toggleCodeWrap"
                class="p-1 hover:bg-gray-200 rounded transition-colors"
                :title="codeWrap ? '取消换行' : '自动换行'"
              >
                <i :class="codeWrap ? 'fas fa-align-left' : 'fas fa-align-justify'"></i>
              </button>
            </div>
          </div>
        </div>
        
        <div class="flex-1 relative min-h-0">
          <textarea
            ref="markdownTextarea"
            v-model="markdownContent"
            @input="debouncedParseMd"
            @keydown="handleKeydown"
            class="w-full h-full p-4 font-mono text-sm resize-none border-none focus:outline-none bg-white transition-colors"
            :class="{ 
              'whitespace-pre-wrap break-words': codeWrap,
              'whitespace-pre overflow-x-auto': !codeWrap
            }"
            placeholder="请输入实体定义...

示例:
# 用户表 (users)
- id: bigint PK AI // 用户ID
- username: varchar(50) UK NN // 用户名
- email: varchar(100) UK NN // 邮箱
- created_at: datetime NN // 创建时间

# 文章表 (posts)  
- id: bigint PK AI // 文章ID
- title: varchar(200) NN // 标题
- user_id: bigint FK NN // 用户ID (关联 users.id)
- created_at: datetime NN // 创建时间"
          ></textarea>
          
          <!-- 语法提示 -->
          <div class="absolute bottom-4 left-4 right-4 bg-blue-50 border border-blue-200 rounded-lg p-3 text-xs shadow-sm">
            <div class="font-medium text-blue-800 mb-2 flex items-center">
              <i class="fas fa-lightbulb mr-1"></i>
              语法提示:
            </div>
            <div class="text-blue-600 space-y-1">
              <div>• <kbd class="px-1 py-0.5 bg-blue-100 rounded text-xs">PK</kbd>: 主键 | <kbd class="px-1 py-0.5 bg-blue-100 rounded text-xs">FK</kbd>: 外键 | <kbd class="px-1 py-0.5 bg-blue-100 rounded text-xs">UK</kbd>: 唯一键</div>
              <div>• <kbd class="px-1 py-0.5 bg-blue-100 rounded text-xs">NN</kbd>: 非空 | <kbd class="px-1 py-0.5 bg-blue-100 rounded text-xs">AI</kbd>: 自增</div>
              <div>• 格式: <code class="px-1 py-0.5 bg-blue-100 rounded text-xs">field_name: data_type [约束] // 注释</code></div>
            </div>
          </div>
        </div>
      </div>

      <!-- 可拖拽的分隔条 -->
      <div 
        ref="resizeHandle"
        class="w-1 bg-gray-300 hover:bg-blue-400 cursor-col-resize transition-colors duration-200 relative group flex-shrink-0"
        @mousedown="startResize"
        title="拖拽调整面板宽度"
      >
        <!-- 分隔条中间的抓手图标 -->
        <div class="absolute top-1/2 left-1/2 transform -translate-x-1/2 -translate-y-1/2 opacity-0 group-hover:opacity-100 transition-opacity">
          <div class="flex space-x-0.5">
            <div class="w-0.5 h-4 bg-white rounded"></div>
            <div class="w-0.5 h-4 bg-white rounded"></div>
            <div class="w-0.5 h-4 bg-white rounded"></div>
          </div>
        </div>
      </div>

      <!-- 右侧图表区域 -->
      <div class="flex-1 flex flex-col min-w-0">
        <!-- 图表工具栏 -->
        <div class="px-4 py-3 bg-gray-50 border-b border-gray-200 flex items-center justify-between flex-shrink-0">
          <h3 class="font-semibold text-gray-800 flex items-center">
            <i class="fas fa-sitemap text-blue-500 mr-2"></i>
            Mermaid ER 图表
          </h3>
          
          <div class="flex items-center space-x-3">
            <!-- 缩放控制 -->
            <div class="flex items-center space-x-2 bg-white border border-gray-300 rounded-lg px-3 py-1 shadow-sm">
              <button
                @click="zoomOut"
                :disabled="currentZoom <= 0.2"
                class="p-1 hover:bg-gray-100 rounded transition-colors disabled:opacity-50 disabled:cursor-not-allowed"
                title="缩小 (Ctrl + -)"
              >
                <i class="fas fa-search-minus text-sm"></i>
              </button>
              
              <span class="text-sm text-gray-600 min-w-[60px] text-center font-mono">
                {{ Math.round(currentZoom * 100) }}%
              </span>
              
              <button
                @click="zoomIn"
                :disabled="currentZoom >= 3"
                class="p-1 hover:bg-gray-100 rounded transition-colors disabled:opacity-50 disabled:cursor-not-allowed"
                title="放大 (Ctrl + +)"
              >
                <i class="fas fa-search-plus text-sm"></i>
              </button>
            </div>
            
            <!-- 视图控制 -->
            <div class="flex items-center space-x-1">
              <button
                @click="fitToScreen"
                class="px-2 py-1 text-sm bg-white border border-gray-300 hover:bg-gray-50 rounded transition-colors shadow-sm"
                title="适合屏幕 (Ctrl + 0)"
              >
                <i class="fas fa-expand-arrows-alt mr-1"></i>
                适合屏幕
              </button>
              
              <button
                @click="resetView"
                class="px-2 py-1 text-sm bg-white border border-gray-300 hover:bg-gray-50 rounded transition-colors shadow-sm"
                title="重置视图 (Ctrl + R)"
              >
                <i class="fas fa-undo mr-1"></i>
                重置
              </button>
            </div>
            
            <!-- 主题选择 -->
            <select 
              v-model="mermaidTheme"
              @change="updateDiagram"
              class="px-3 py-1 text-sm border border-gray-300 rounded-lg focus:outline-none focus:ring-2 focus:ring-blue-500 bg-white shadow-sm"
            >
              <option value="default">默认主题</option>
              <option value="dark">深色主题</option>
              <option value="forest">森林主题</option>
              <option value="neutral">中性主题</option>
            </select>
            
            <button
              @click="viewDbml"
              class="px-3 py-1 text-sm bg-gray-200 hover:bg-gray-300 rounded-lg transition-colors shadow-sm"
            >
              <i class="fas fa-code mr-1"></i>
              查看 DBML
            </button>
            
            <button
              @click="clearDiagram"
              class="px-3 py-1 text-sm bg-red-500 text-white hover:bg-red-600 rounded-lg transition-colors shadow-sm"
            >
              <i class="fas fa-trash mr-1"></i>
              清空
            </button>
          </div>
        </div>
                
        <!-- Mermaid 图表容器 -->
        <div class="flex-1 relative bg-white overflow-hidden">
          <div 
            ref="mermaidContainer" 
            class="w-full h-full min-h-[400px] relative cursor-grab active:cursor-grabbing select-none" 
            id="mermaid-diagram"
            @mousedown="startPan"
            @mousemove="doPan"
            @mouseup="endPan"
            @mouseleave="endPan"
            @wheel="handleWheel"
            @keydown="handleCanvasKeydown"
            tabindex="0"
            :style="{
              transform: `scale(${currentZoom}) translate(${panX}px, ${panY}px)`,
              transformOrigin: 'center center',
              transition: isTransitioning ? 'transform 0.3s ease' : 'none'
            }"
          >
            <!-- 默认提示 -->
            <div v-if="!mermaidCode && !isLoading" class="absolute inset-0 flex items-center justify-center text-gray-500">
              <div class="text-center">
                <i class="fas fa-sitemap text-4xl mb-4 text-gray-300"></i>
                <div class="text-lg font-medium">请在左侧输入实体定义</div>
                <div class="text-sm">图表将在这里显示</div>
                <div class="text-xs mt-3 text-gray-400 space-y-1">
                  <div>支持鼠标滚轮缩放，拖拽平移</div>
                  <div>快捷键: Ctrl+0 适合屏幕, Ctrl+R 重置视图</div>
                </div>
              </div>
            </div>
            
            <!-- Mermaid 渲染区域 -->
            <div ref="mermaidSvgContainer" class="w-full h-full flex items-center justify-center"></div>
          </div>
          
          <!-- 缩放指示器和快捷键提示 -->
          <div v-if="mermaidCode" class="absolute bottom-4 right-4 bg-black bg-opacity-70 text-white text-xs px-3 py-2 rounded-lg backdrop-blur-sm">
            <div class="flex items-center space-x-2">
              <span>缩放: {{ Math.round(currentZoom * 100) }}%</span>
              <span>|</span>
              <span>拖拽平移</span>
            </div>
          </div>

          <!-- 快捷键提示 -->
          <div v-if="showShortcutHints" class="absolute bottom-4 left-4 bg-black bg-opacity-70 text-white text-xs px-3 py-2 rounded-lg backdrop-blur-sm">
            <div class="space-y-1">
              <div><kbd class="px-1 py-0.5 bg-gray-600 rounded text-xs">Ctrl+0</kbd> 适合屏幕</div>
              <div><kbd class="px-1 py-0.5 bg-gray-600 rounded text-xs">Ctrl+R</kbd> 重置视图</div>
              <div><kbd class="px-1 py-0.5 bg-gray-600 rounded text-xs">F11</kbd> 全屏切换</div>
            </div>
          </div>
          
          <!-- 加载状态 -->
          <div v-if="isLoading" class="absolute inset-0 bg-white bg-opacity-75 flex items-center justify-center backdrop-blur-sm">
            <div class="text-center">
              <div class="animate-spin rounded-full h-8 w-8 border-b-2 border-blue-500 mx-auto mb-3"></div>
              <div class="text-gray-600 font-medium">正在生成图表...</div>
            </div>
          </div>

          <!-- 错误状态 -->
          <div v-if="errorMessage" class="absolute inset-0 bg-red-50 flex items-center justify-center">
            <div class="text-center max-w-md mx-4">
              <i class="fas fa-exclamation-triangle text-3xl text-red-500 mb-3"></i>
              <div class="text-red-700 font-medium text-lg">图表渲染失败</div>
              <div class="text-red-600 text-sm mt-2 bg-red-100 p-3 rounded-lg">{{ errorMessage }}</div>
              <button 
                @click="retryRender"
                class="mt-4 px-4 py-2 bg-red-500 text-white rounded-lg hover:bg-red-600 transition-colors shadow-sm"
              >
                <i class="fas fa-redo mr-2"></i>
                重试
              </button>
            </div>
          </div>
        </div>
      </div>
    </div>

    <!-- 底部状态栏 -->
    <footer class="bg-white border-t border-gray-200 px-6 py-3 flex-shrink-0" v-show="!isFullscreen">
      <div class="flex items-center justify-between text-sm text-gray-600">
        <div class="flex items-center space-x-4">
          <span class="flex items-center">
            <i class="fas fa-table mr-1 text-blue-500"></i>
            实体数量: <strong class="text-gray-800 ml-1">{{ entityCount }}</strong>
          </span>
          <span class="flex items-center">
            <i class="fas fa-link mr-1 text-green-500"></i>
            关系数量: <strong class="text-gray-800 ml-1">{{ relationshipCount }}</strong>
          </span>
          <span v-if="dbmlContent" class="flex items-center">
            <i class="fas fa-file-code mr-1 text-purple-500"></i>
            DBML 长度: <strong class="text-gray-800 ml-1">{{ dbmlContent.length }}</strong> 字符
          </span>
        </div>
        <div class="flex items-center space-x-4">
          <span v-if="lastUpdateTime" class="flex items-center">
            <i class="fas fa-clock mr-1 text-gray-400"></i>
            最后更新: {{ lastUpdateTime }}
          </span>
          <span class="flex items-center" v-if="!isLoading && !errorMessage">
            <div class="w-2 h-2 bg-green-500 rounded-full mr-2 animate-pulse"></div>
            已同步
          </span>
          <span class="flex items-center text-red-600" v-if="errorMessage">
            <div class="w-2 h-2 bg-red-500 rounded-full mr-2"></div>
            错误
          </span>
        </div>
      </div>
    </footer>

    <!-- SQL 生成结果弹窗 -->
    <div v-if="showSQLModal" class="fixed inset-0 bg-black bg-opacity-50 flex items-center justify-center z-50 p-4">
      <div class="bg-white rounded-xl shadow-2xl max-w-4xl w-full max-h-[80vh] flex flex-col">
        <div class="px-6 py-4 border-b border-gray-200 flex items-center justify-between flex-shrink-0">
          <h3 class="text-lg font-semibold text-gray-800">
            <i class="fas fa-database text-blue-500 mr-2"></i>
            生成的 SQL 语句 (基于 DBML)
          </h3>
          <div class="flex items-center space-x-2">
            <select 
              v-model="sqlDialect"
              @change="generateSQLFromDbml"
              class="px-3 py-2 text-sm border border-gray-300 rounded-lg focus:outline-none focus:ring-2 focus:ring-blue-500"
            >
              <option value="postgres">PostgreSQL</option>
              <option value="mysql">MySQL</option>
              <option value="mssql">SQL Server</option>
              <option value="oracle">Oracle</option>
            </select>
            <button
              @click="copySQL"
              class="px-4 py-2 bg-blue-500 text-white rounded-lg hover:bg-blue-600 transition-colors"
            >
              <i class="fas fa-copy mr-2"></i>
              复制
            </button>
            <button
              @click="showSQLModal = false"
              class="p-2 hover:bg-gray-100 rounded-lg transition-colors"
            >
              <i class="fas fa-times"></i>
            </button>
          </div>
        </div>
        <div class="flex-1 overflow-auto p-6">
          <pre class="bg-gray-100 p-4 rounded-lg text-sm font-mono whitespace-pre-wrap">{{ generatedSQL }}</pre>
        </div>
      </div>
    </div>

    <!-- DBML 查看弹窗 -->
    <div v-if="showDbmlModal" class="fixed inset-0 bg-black bg-opacity-50 flex items-center justify-center z-50 p-4">
      <div class="bg-white rounded-xl shadow-2xl max-w-4xl w-full max-h-[80vh] flex flex-col">
        <div class="px-6 py-4 border-b border-gray-200 flex items-center justify-between flex-shrink-0">
          <h3 class="text-lg font-semibold text-gray-800">
            <i class="fas fa-code text-green-500 mr-2"></i>
            DBML 结构定义
          </h3>
          <div class="flex items-center space-x-2">
            <button
              @click="copyDbml"
              class="px-4 py-2 bg-green-500 text-white rounded-lg hover:bg-green-600 transition-colors"
            >
              <i class="fas fa-copy mr-2"></i>
              复制 DBML
            </button>
            <button
              @click="showDbmlModal = false"
              class="p-2 hover:bg-gray-100 rounded-lg transition-colors"
            >
              <i class="fas fa-times"></i>
            </button>
          </div>
        </div>
        <div class="flex-1 overflow-auto p-6">
          <pre class="bg-gray-100 p-4 rounded-lg text-sm font-mono whitespace-pre-wrap">{{ dbmlContent }}</pre>
        </div>
      </div>
    </div>
  </div>
</template>

<script setup lang="ts">
import { ref, onMounted, onUnmounted, nextTick, computed } from 'vue'
import mermaid from 'mermaid'

// 响应式数据
const mermaidContainer = ref<HTMLElement | null>(null)
const mermaidSvgContainer = ref<HTMLElement | null>(null)
const markdownTextarea = ref<HTMLTextAreaElement | null>(null)
const resizeHandle = ref<HTMLElement | null>(null)
const markdownContent = ref('')
const selectedTemplate = ref('')
const generatedSQL = ref('')
const showSQLModal = ref(false)
const showDbmlModal = ref(false)
const isLoading = ref(false)
const errorMessage = ref('')
const lastUpdateTime = ref('')
const diagramDirection = ref('TB')
const mermaidTheme = ref('default')
const sqlDialect = ref('postgres')

// 全屏相关
const isFullscreen = ref(false)

// 面板拖拽相关
const leftPanelWidth = ref(window.innerWidth * 0.33) // 默认1/3宽度
const isResizing = ref(false)
const startX = ref(0)
const startWidth = ref(0)

// 代码编辑器相关
const codeWrap = ref(false)
const showShortcutHints = ref(false)

// 画布交互相关
const currentZoom = ref(1)
const panX = ref(0)
const panY = ref(0)
const isPanning = ref(false)
const isTransitioning = ref(false)
const lastMouseX = ref(0)
const lastMouseY = ref(0)

// 数据存储
const dbmlContent = ref('')
const mermaidCode = ref('')
const entities = ref<any[]>([])
const relationships = ref<any[]>([])

// 计算属性
const entityCount = computed(() => {
  console.log('计算实体数量:', entities.value.length)
  return entities.value.length
})
const relationshipCount = computed(() => {
  console.log('计算关系数量:', relationships.value.length)
  return relationships.value.length
})

// 接口定义
interface Entity {
  name: string
  tableName: string
  fields: Field[]
}

interface Field {
  name: string
  type: string
  constraints: string[]
  comment: string
  isPrimaryKey: boolean
  isForeignKey: boolean
  isUnique: boolean
  isNotNull: boolean
  isAutoIncrement: boolean
  foreignRef?: string
}

// 模板数据
const templates: Record<string, string> = {
  ecommerce: `# 用户表 (users)
- id: bigint PK AI // 用户ID
- username: varchar(50) UK NN // 用户名
- email: varchar(100) UK NN // 邮箱地址
- password_hash: varchar(255) NN // 密码哈希
- phone: varchar(20) // 手机号
- created_at: datetime NN // 创建时间
- updated_at: datetime NN // 更新时间

# 商品分类表 (categories)
- id: bigint PK AI // 分类ID
- name: varchar(100) NN // 分类名称
- parent_id: bigint FK // 父分类ID (关联 categories.id)
- sort_order: int NN // 排序
- created_at: datetime NN // 创建时间

# 商品表 (products)
- id: bigint PK AI // 商品ID
- name: varchar(200) NN // 商品名称
- description: text // 商品描述
- price: decimal(10,2) NN // 价格
- stock: int NN // 库存
- category_id: bigint FK NN // 分类ID (关联 categories.id)
- seller_id: bigint FK NN // 卖家ID (关联 users.id)
- status: tinyint NN // 状态
- created_at: datetime NN // 创建时间

# 订单表 (orders)
- id: bigint PK AI // 订单ID
- order_no: varchar(50) UK NN // 订单号
- user_id: bigint FK NN // 用户ID (关联 users.id)
- total_amount: decimal(10,2) NN // 总金额
- status: tinyint NN // 订单状态
- created_at: datetime NN // 创建时间

# 订单商品表 (order_items)
- id: bigint PK AI // 记录ID
- order_id: bigint FK NN // 订单ID (关联 orders.id)
- product_id: bigint FK NN // 商品ID (关联 products.id)
- quantity: int NN // 数量
- price: decimal(10,2) NN // 单价
- created_at: datetime NN // 创建时间`,

  blog: `# 用户表 (users)
- id: bigint PK AI // 用户ID
- username: varchar(50) UK NN // 用户名
- email: varchar(100) UK NN // 邮箱
- password_hash: varchar(255) NN // 密码哈希
- avatar: varchar(255) // 头像URL
- bio: text // 个人简介
- created_at: datetime NN // 创建时间

# 分类表 (categories)
- id: bigint PK AI // 分类ID
- name: varchar(100) NN // 分类名称
- slug: varchar(100) UK NN // URL别名
- description: text // 分类描述
- created_at: datetime NN // 创建时间

# 文章表 (posts)
- id: bigint PK AI // 文章ID
- title: varchar(200) NN // 文章标题
- slug: varchar(200) UK NN // URL别名
- content: longtext NN // 文章内容
- excerpt: text // 摘要
- author_id: bigint FK NN // 作者ID (关联 users.id)
- category_id: bigint FK // 分类ID (关联 categories.id)
- status: tinyint NN // 发布状态
- published_at: datetime // 发布时间
- created_at: datetime NN // 创建时间

# 评论表 (comments)
- id: bigint PK AI // 评论ID
- post_id: bigint FK NN // 文章ID (关联 posts.id)
- user_id: bigint FK NN // 用户ID (关联 users.id)
- parent_id: bigint FK // 父评论ID (关联 comments.id)
- content: text NN // 评论内容
- status: tinyint NN // 审核状态
- created_at: datetime NN // 创建时间

# 标签表 (tags)
- id: bigint PK AI // 标签ID
- name: varchar(50) UK NN // 标签名称
- slug: varchar(50) UK NN // URL别名
- created_at: datetime NN // 创建时间

# 文章标签关联表 (post_tags)
- id: bigint PK AI // 关联ID
- post_id: bigint FK NN // 文章ID (关联 posts.id)
- tag_id: bigint FK NN // 标签ID (关联 tags.id)
- created_at: datetime NN // 创建时间`,

  crm: `# 客户表 (customers)
- id: bigint PK AI // 客户ID
- name: varchar(200) NN // 客户名称
- company: varchar(200) // 公司名称
- phone: varchar(50) // 电话
- email: varchar(100) // 邮箱
- address: text // 地址
- industry: varchar(100) // 行业
- source: varchar(50) // 客户来源
- created_at: datetime NN // 创建时间

# 销售人员表 (sales_reps)
- id: bigint PK AI // 销售ID
- name: varchar(100) NN // 姓名
- email: varchar(100) UK NN // 邮箱
- phone: varchar(50) // 电话
- department: varchar(100) // 部门
- created_at: datetime NN // 创建时间

# 销售机会表 (opportunities)
- id: bigint PK AI // 机会ID
- title: varchar(200) NN // 机会标题
- customer_id: bigint FK NN // 客户ID (关联 customers.id)
- sales_rep_id: bigint FK NN // 销售人员ID (关联 sales_reps.id)
- amount: decimal(12,2) // 预期金额
- stage: varchar(50) NN // 销售阶段
- probability: int // 成功概率
- close_date: date // 预计成交日期
- created_at: datetime NN // 创建时间

# 跟进记录表 (activities)
- id: bigint PK AI // 记录ID
- customer_id: bigint FK NN // 客户ID (关联 customers.id)
- opportunity_id: bigint FK // 机会ID (关联 opportunities.id)
- sales_rep_id: bigint FK NN // 销售人员ID (关联 sales_reps.id)
- type: varchar(50) NN // 活动类型
- subject: varchar(200) NN // 主题
- description: text // 描述
- activity_date: datetime NN // 活动时间
- created_at: datetime NN // 创建时间`
}

// 防抖解析
let parseTimeout: NodeJS.Timeout | null = null
const debouncedParseMd = () => {
  if (parseTimeout) {
    clearTimeout(parseTimeout)
  }
  parseTimeout = setTimeout(() => {
    parseMarkdownToDbml()
  }, 500)
}

// 全屏功能
function toggleFullscreen() {
  isFullscreen.value = !isFullscreen.value
  
  if (isFullscreen.value) {
    // 进入全屏模式
    document.documentElement.requestFullscreen?.()
    showShortcutHints.value = true
    setTimeout(() => {
      showShortcutHints.value = false
    }, 3000)
  } else {
    // 退出全屏模式
    document.exitFullscreen?.()
  }
}

// 面板拖拽功能
function startResize(event: MouseEvent) {
  isResizing.value = true
  startX.value = event.clientX
  startWidth.value = leftPanelWidth.value
  event.preventDefault()
  
  document.addEventListener('mousemove', doResize)
  document.addEventListener('mouseup', endResize)
  document.body.style.cursor = 'col-resize'
  document.body.style.userSelect = 'none'
}

function doResize(event: MouseEvent) {
  if (!isResizing.value) return
  
  const deltaX = event.clientX - startX.value
  const newWidth = startWidth.value + deltaX
  const containerWidth = window.innerWidth
  
  // 限制面板宽度在合理范围内
  const minWidth = 300
  const maxWidth = containerWidth * 0.7
  
  if (newWidth >= minWidth && newWidth <= maxWidth) {
    leftPanelWidth.value = newWidth
  }
}

function endResize() {
  isResizing.value = false
  document.removeEventListener('mousemove', doResize)
  document.removeEventListener('mouseup', endResize)
  document.body.style.cursor = ''
  document.body.style.userSelect = ''
}

// 代码编辑器功能
function toggleCodeWrap() {
  codeWrap.value = !codeWrap.value
}

function handleKeydown(event: KeyboardEvent) {
  // Tab 键插入缩进
  if (event.key === 'Tab') {
    event.preventDefault()
    const textarea = event.target as HTMLTextAreaElement
    const start = textarea.selectionStart
    const end = textarea.selectionEnd
    
    if (event.shiftKey) {
      // Shift+Tab 减少缩进
      const beforeCursor = markdownContent.value.substring(0, start)
      const afterCursor = markdownContent.value.substring(end)
      
      if (beforeCursor.endsWith('  ')) {
        markdownContent.value = beforeCursor.slice(0, -2) + afterCursor
        nextTick(() => {
          textarea.setSelectionRange(start - 2, end - 2)
        })
      }
    } else {
      // Tab 增加缩进
      markdownContent.value = markdownContent.value.substring(0, start) + '  ' + markdownContent.value.substring(end)
      nextTick(() => {
        textarea.setSelectionRange(start + 2, start + 2)
      })
    }
  }
  
  // Ctrl+/ 切换注释
  if (event.ctrlKey && event.key === '/') {
    event.preventDefault()
    toggleComment()
  }
}

function toggleComment() {
  const textarea = markdownTextarea.value
  if (!textarea) return
  
  const start = textarea.selectionStart
  const end = textarea.selectionEnd
  const lines = markdownContent.value.split('\n')
  
  // 找到选中的行
  let startLine = 0
  let endLine = 0
  let charCount = 0
  
  for (let i = 0; i < lines.length; i++) {
    if (charCount <= start && start <= charCount + lines[i].length) {
      startLine = i
    }
    if (charCount <= end && end <= charCount + lines[i].length) {
      endLine = i
      break
    }
    charCount += lines[i].length + 1
  }
  
  // 切换注释
  for (let i = startLine; i <= endLine; i++) {
    if (lines[i].trim().startsWith('//')) {
      lines[i] = lines[i].replace(/^\s*\/\/\s?/, '')
    } else if (lines[i].trim()) {
      lines[i] = '// ' + lines[i]
    }
  }
  
  markdownContent.value = lines.join('\n')
  debouncedParseMd()
}

// 画布快捷键
function handleCanvasKeydown(event: KeyboardEvent) {
  if (event.ctrlKey) {
    switch (event.key) {
      case '0':
        event.preventDefault()
        fitToScreen()
        break
      case 'r':
      case 'R':
        event.preventDefault()
        resetView()
        break
      case '=':
      case '+':
        event.preventDefault()
        zoomIn()
        break
      case '-':
        event.preventDefault()
        zoomOut()
        break
    }
  }
  
  if (event.key === 'F11') {
    event.preventDefault()
    toggleFullscreen()
  }
}

// 监听全屏变化
function handleFullscreenChange() {
  isFullscreen.value = !!document.fullscreenElement
}

// 窗口大小变化处理
function handleResize() {
  // 调整左面板宽度，确保不超过最大限制
  const maxWidth = window.innerWidth * 0.7
  if (leftPanelWidth.value > maxWidth) {
    leftPanelWidth.value = maxWidth
  }
}

// 初始化 Mermaid
function initMermaid() {
  mermaid.initialize({
    startOnLoad: false,
    theme: mermaidTheme.value as any,
    er: {
      layoutDirection: diagramDirection.value as any,
      useMaxWidth: true,
      fontSize: 12
    },
    flowchart: {
      useMaxWidth: true
    }
  })
}

// 解析 Markdown 并转换为 DBML
function parseMarkdownToDbml() {
  if (!markdownContent.value.trim()) {
    entities.value = []
    relationships.value = []
    dbmlContent.value = ''
    mermaidCode.value = ''
    updateDiagram()
    return
  }

  isLoading.value = true
  errorMessage.value = ''
  
  try {
    console.log('开始解析 Markdown:', markdownContent.value.length, '字符')
    
    const lines = markdownContent.value.split('\n').filter(line => line.trim())
    const newEntities: Entity[] = []
    const newRelationships: any[] = []
    
    let currentEntity: Entity | null = null
    
    for (const line of lines) {
      const trimmedLine = line.trim()
      
      // 解析实体标题
      if (trimmedLine.startsWith('#')) {
        if (currentEntity) {
          newEntities.push(currentEntity)
        }
        
        const match = trimmedLine.match(/^#+\s*(.+?)\s*\(([^)]+)\)/)
        if (match) {
          currentEntity = {
            name: match[1].trim(),
            tableName: match[2].trim(),
            fields: []
          }
        }
      }
      // 解析字段
      else if (trimmedLine.startsWith('-') && currentEntity) {
        const fieldMatch = trimmedLine.match(/^-\s*([^:]+):\s*([^/]+)(?:\/\/\s*(.*))?/)
        if (fieldMatch) {
          const fieldName = fieldMatch[1].trim()
          const typeAndConstraints = fieldMatch[2].trim()
          const comment = fieldMatch[3]?.trim() || ''
          
          // 分离类型和约束
          const parts = typeAndConstraints.split(/\s+/)
          const type = parts[0]
          const constraints = parts.slice(1)
          
          // 检查外键关联
          const foreignRefMatch = comment.match(/关联\s+(\w+)\.(\w+)|关联\s+(\w+\.\w+)/)
          let foreignRef = ''
          if (foreignRefMatch) {
            foreignRef = foreignRefMatch[1] ? `${foreignRefMatch[1]}.${foreignRefMatch[2]}` : foreignRefMatch[3]
          }
          
          const field: Field = {
            name: fieldName,
            type: type,
            constraints: constraints,
            comment: comment,
            isPrimaryKey: constraints.includes('PK'),
            isForeignKey: constraints.includes('FK'),
            isUnique: constraints.includes('UK'),
            isNotNull: constraints.includes('NN'),
            isAutoIncrement: constraints.includes('AI'),
            foreignRef: foreignRef
          }
          
          currentEntity.fields.push(field)
          
          // 如果是外键，创建关系
          if (field.isForeignKey && field.foreignRef) {
            const [refTable, refField] = field.foreignRef.split('.')
            newRelationships.push({
              from: field.foreignRef,
              to: `${currentEntity.tableName}.${field.name}`,
              type: 'one-to-many'
            })
          }
        }
      }
    }
    
    if (currentEntity) {
      newEntities.push(currentEntity)
    }
    
    console.log('解析完成:', newEntities.length, '个实体,', newRelationships.length, '个关系')
    
    entities.value = newEntities
    relationships.value = newRelationships
    
    // 生成 DBML
    generateDbmlFromEntities()
    
    // 生成 Mermaid
    generateMermaidFromEntities()
    
    lastUpdateTime.value = new Date().toLocaleTimeString()
  } catch (error) {
    console.error('解析 Markdown 失败:', error)
    errorMessage.value = '解析失败: ' + (error as Error).message
  } finally {
    isLoading.value = false
  }
}

// 从实体生成 DBML
function generateDbmlFromEntities() {
  if (entities.value.length === 0) {
    dbmlContent.value = ''
    return
  }
  
  let dbml = '// Generated DBML from Markdown\n\n'
  
  // 生成表定义
  entities.value.forEach(entity => {
    dbml += `Table ${entity.tableName} {\n`
    
    entity.fields.forEach(field => {
      let fieldDef = `  ${field.name} ${field.type}`
      
      // 添加约束
      const constraints: string[] = []
      if (field.isPrimaryKey) constraints.push('pk')
      if (field.isUnique && !field.isPrimaryKey) constraints.push('unique')
      if (field.isNotNull) constraints.push('not null')
      if (field.isAutoIncrement) constraints.push('increment')
      
      if (constraints.length > 0) {
        fieldDef += ` [${constraints.join(', ')}]`
      }
      
      if (field.comment) {
        fieldDef += ` // ${field.comment}`
      }
      
      dbml += fieldDef + '\n'
    })
    
    dbml += `}\n\n`
  })
  
  // 生成关系定义
  relationships.value.forEach(rel => {
    dbml += `Ref: ${rel.from} > ${rel.to}\n`
  })
  
  dbmlContent.value = dbml
}

// 从实体生成 Mermaid ER 图
function generateMermaidFromEntities() {
  if (entities.value.length === 0) {
    mermaidCode.value = ''
    updateDiagram()
    return
  }
  
  let mermaid = `erDiagram\n`
  mermaid += `    direction ${diagramDirection.value}\n`
  
  // 生成实体定义
  entities.value.forEach(entity => {
    mermaid += `    ${entity.tableName.toUpperCase()} {\n`
    
    entity.fields.forEach(field => {
      // 清理字段类型，移除不支持的字符
      let cleanType = field.type
        .replace(/\([^)]*\)/g, '') // 移除括号和内容，如 varchar(50) -> varchar
        .replace(/[,\(\)]/g, '') // 移除逗号和括号
        .trim()
      
      // 特殊类型映射
      const typeMapping: Record<string, string> = {
        'varchar': 'string',
        'text': 'string',
        'longtext': 'string',
        'bigint': 'int',
        'tinyint': 'int',
        'decimal': 'float',
        'datetime': 'string',
        'date': 'string',
        'timestamp': 'string'
      }
      
      cleanType = typeMapping[cleanType] || cleanType
      
      let fieldLine = `        ${cleanType} ${field.name}`
      
      // 添加约束标记
      const constraints: string[] = []
      if (field.isPrimaryKey) constraints.push('PK')
      if (field.isForeignKey) constraints.push('FK')
      if (field.isUnique && !field.isPrimaryKey) constraints.push('UK')
      
      if (constraints.length > 0) {
        fieldLine += ` ${constraints.join(',')}`
      }
      
      if (field.comment) {
        // 清理注释中的特殊字符
        const cleanComment = field.comment.replace(/["\(\)]/g, '').trim()
        fieldLine += ` "${cleanComment}"`
      }
      
      mermaid += fieldLine + '\n'
    })
    
    mermaid += '    }\n'
  })
  
  // 生成关系
  relationships.value.forEach(rel => {
    const [fromTable, fromField] = rel.from.split('.')
    const [toTable, toField] = rel.to.split('.')
    
    // Mermaid ER 图关系语法
    mermaid += `    ${fromTable.toUpperCase()} ||--o{ ${toTable.toUpperCase()} : "has"\n`
  })
  
  mermaidCode.value = mermaid
  updateDiagram()
}

// 更新 Mermaid 图表
async function updateDiagram() {
  if (!mermaidSvgContainer.value || !mermaidCode.value) {
    console.log('容器或代码为空，跳过渲染')
    return
  }
  
  try {
    isLoading.value = true
    errorMessage.value = ''
    
    console.log('开始渲染 Mermaid 图表:', mermaidCode.value)
    
    // 重新初始化 Mermaid 以应用新的配置
    mermaid.initialize({
      startOnLoad: false,
      theme: mermaidTheme.value as any,
      er: {
        layoutDirection: diagramDirection.value as any,
        useMaxWidth: false, // 改为 false 以便自定义缩放
        fontSize: 12
      },
      securityLevel: 'loose'
    })
    
    // 清空容器
    mermaidSvgContainer.value.innerHTML = ''
    
    // 创建一个唯一的图表ID
    const diagramId = `mermaid-${Date.now()}`
    
    // 渲染新图表
    const renderResult = await mermaid.render(diagramId, mermaidCode.value) as any
    const svg = renderResult.svg || renderResult
    mermaidSvgContainer.value.innerHTML = svg
    
    // 渲染完成后，自动适合屏幕
    nextTick(() => {
      const svgElement = mermaidSvgContainer.value?.querySelector('svg')
      if (svgElement) {
        // 设置SVG的基本样式
        svgElement.style.maxWidth = 'none'
        svgElement.style.height = 'auto'
        
        // 如果是第一次渲染，自动适合屏幕
        if (currentZoom.value === 1 && panX.value === 0 && panY.value === 0) {
          setTimeout(() => {
            fitToScreen()
          }, 100)
        }
      }
    })
    
    console.log('Mermaid 图表渲染成功')
  } catch (error) {
    console.error('Mermaid 渲染错误:', error)
    errorMessage.value = 'Mermaid 渲染失败: ' + (error as Error).message
    
    // 如果渲染失败，显示原始代码用于调试
    if (mermaidSvgContainer.value) {
      mermaidSvgContainer.value.innerHTML = `
        <div class="text-left p-4">
          <div class="text-red-600 font-medium mb-2">渲染失败，原始代码:</div>
          <pre class="bg-gray-100 p-4 rounded text-sm overflow-auto">${mermaidCode.value}</pre>
        </div>
      `
    }
  } finally {
    isLoading.value = false
  }
}

// 重试渲染
function retryRender() {
  console.log('重试渲染图表')
  errorMessage.value = ''
  updateDiagram()
}

// 工具栏功能
function loadTemplate() {
  if (selectedTemplate.value && templates[selectedTemplate.value]) {
    markdownContent.value = templates[selectedTemplate.value]
    parseMarkdownToDbml()
  }
}

function formatMarkdown() {
  // 格式化当前的 Markdown 内容
  parseMarkdownToDbml()
}

function generateSQL() {
  if (!dbmlContent.value) {
    generatedSQL.value = '// 请先定义实体'
    showSQLModal.value = true
    return
  }
  
  generateSQLFromDbml()
  showSQLModal.value = true
}

function generateSQLFromDbml() {
  // 这里应该使用 @dbml/core 来生成 SQL
  // 由于无法在浏览器中直接使用 @dbml/core，我们使用简化的 SQL 生成
  generateSimpleSQL()
}

function generateSimpleSQL() {
  if (entities.value.length === 0) {
    generatedSQL.value = '-- 请先定义实体'
    return
  }
  
  const dialectConfig = {
    postgres: {
      autoIncrement: 'SERIAL',
      primaryKey: 'PRIMARY KEY',
      unique: 'UNIQUE',
      notNull: 'NOT NULL',
      foreignKey: 'REFERENCES'
    },
    mysql: {
      autoIncrement: 'AUTO_INCREMENT',
      primaryKey: 'PRIMARY KEY',
      unique: 'UNIQUE',
      notNull: 'NOT NULL',
      foreignKey: 'REFERENCES'
    }
  }
  
  const config = dialectConfig[sqlDialect.value as keyof typeof dialectConfig] || dialectConfig.postgres
  
  let sql = `-- Generated SQL (${sqlDialect.value.toUpperCase()})\n-- Based on DBML conversion\n\n`
  
  entities.value.forEach(entity => {
    sql += `CREATE TABLE ${entity.tableName} (\n`
    
    const fieldSQLs = entity.fields.map(field => {
      let fieldSQL = `  ${field.name} ${field.type.toUpperCase()}`
      
      if (field.isAutoIncrement && sqlDialect.value === 'postgres') {
        fieldSQL = `  ${field.name} SERIAL`
      } else if (field.isAutoIncrement && sqlDialect.value === 'mysql') {
        fieldSQL += ` ${config.autoIncrement}`
      }
      
      if (field.isNotNull) {
        fieldSQL += ` ${config.notNull}`
      }
      
      if (field.isPrimaryKey) {
        fieldSQL += ` ${config.primaryKey}`
      }
      
      if (field.isUnique && !field.isPrimaryKey) {
        fieldSQL += ` ${config.unique}`
      }
      
      return fieldSQL
    })
    
    sql += fieldSQLs.join(',\n') + '\n'
    sql += `);\n\n`
    
    // 添加注释
    if (sqlDialect.value === 'postgres') {
      sql += `COMMENT ON TABLE ${entity.tableName} IS '${entity.name}';\n`
      entity.fields.forEach(field => {
        if (field.comment) {
          sql += `COMMENT ON COLUMN ${entity.tableName}.${field.name} IS '${field.comment}';\n`
        }
      })
      sql += '\n'
    }
  })
  
  generatedSQL.value = sql
}

function exportDiagram() {
  if (!mermaidSvgContainer.value) return
  
  try {
    // 导出 SVG
    const svgElement = mermaidSvgContainer.value.querySelector('svg')
    if (svgElement) {
      const svgData = new XMLSerializer().serializeToString(svgElement)
      const blob = new Blob([svgData], { type: 'image/svg+xml' })
      const url = URL.createObjectURL(blob)
      
      const link = document.createElement('a')
      link.download = 'er-diagram.svg'
      link.href = url
      link.click()
      
      URL.revokeObjectURL(url)
    }
  } catch (error) {
    console.error('导出失败:', error)
    alert('导出功能失败，请稍后重试')
  }
}

function viewDbml() {
  showDbmlModal.value = true
}

function copySQL() {
  copyToClipboard(generatedSQL.value, 'SQL 已复制到剪贴板')
}

function copyDbml() {
  copyToClipboard(dbmlContent.value, 'DBML 已复制到剪贴板')
}

function copyToClipboard(text: string, successMessage: string) {
  if (!text) return
  
  try {
    if (navigator.clipboard && navigator.clipboard.writeText) {
      navigator.clipboard.writeText(text).then(() => {
        console.log(successMessage)
      }).catch(() => {
        fallbackCopy(text, successMessage)
      })
    } else {
      fallbackCopy(text, successMessage)
    }
  } catch (error) {
    console.error('复制操作失败:', error)
  }
}

function fallbackCopy(text: string, successMessage: string) {
  try {
    const textArea = document.createElement('textarea')
    textArea.value = text
    textArea.style.position = 'fixed'
    textArea.style.left = '-999999px'
    textArea.style.top = '-999999px'
    document.body.appendChild(textArea)
    textArea.focus()
    textArea.select()
    document.execCommand('copy')
    document.body.removeChild(textArea)
    console.log(successMessage)
  } catch (error) {
    console.error('备用复制方法也失败:', error)
  }
}

function clearDiagram() {
  if (confirm('确定要清空所有内容吗？')) {
    markdownContent.value = ''
    entities.value = []
    relationships.value = []
    dbmlContent.value = ''
    mermaidCode.value = ''
    if (mermaidSvgContainer.value) {
      mermaidSvgContainer.value.innerHTML = ''
    }
  }
}

// 画布缩放和平移功能
function zoomIn() {
  if (currentZoom.value < 3) {
    currentZoom.value = Math.min(3, currentZoom.value + 0.2)
  }
}

function zoomOut() {
  if (currentZoom.value > 0.2) {
    currentZoom.value = Math.max(0.2, currentZoom.value - 0.2)
  }
}

function resetView() {
  isTransitioning.value = true
  currentZoom.value = 1
  panX.value = 0
  panY.value = 0
  setTimeout(() => {
    isTransitioning.value = false
  }, 300)
}

function fitToScreen() {
  if (!mermaidContainer.value || !mermaidSvgContainer.value) return
  
  const container = mermaidContainer.value
  const svgElement = mermaidSvgContainer.value.querySelector('svg')
  
  if (svgElement) {
    const containerRect = container.getBoundingClientRect()
    const svgRect = svgElement.getBoundingClientRect()
    
    // 计算适合的缩放比例
    const scaleX = (containerRect.width * 0.9) / svgRect.width
    const scaleY = (containerRect.height * 0.9) / svgRect.height
    const optimalScale = Math.min(scaleX, scaleY, 2) // 最大不超过2倍
    
    isTransitioning.value = true
    currentZoom.value = Math.max(0.2, optimalScale)
    panX.value = 0
    panY.value = 0
    
    setTimeout(() => {
      isTransitioning.value = false
    }, 300)
  }
}

function handleWheel(event: WheelEvent) {
  event.preventDefault()
  
  const delta = event.deltaY > 0 ? -0.1 : 0.1
  const newZoom = currentZoom.value + delta
  
  if (newZoom >= 0.2 && newZoom <= 3) {
    currentZoom.value = newZoom
  }
}

function startPan(event: MouseEvent) {
  if (event.button === 0) { // 只响应左键
    isPanning.value = true
    lastMouseX.value = event.clientX
    lastMouseY.value = event.clientY
    event.preventDefault()
  }
}

function doPan(event: MouseEvent) {
  if (isPanning.value) {
    const deltaX = event.clientX - lastMouseX.value
    const deltaY = event.clientY - lastMouseY.value
    
    panX.value += deltaX / currentZoom.value
    panY.value += deltaY / currentZoom.value
    
    lastMouseX.value = event.clientX
    lastMouseY.value = event.clientY
    event.preventDefault()
  }
}

function endPan() {
  isPanning.value = false
}

// 生命周期
onMounted(async () => {
  console.log('组件挂载，初始化 Mermaid')
  await nextTick()
  
  // 初始化 Mermaid
  try {
    mermaid.initialize({
      startOnLoad: false,
      theme: 'default',
      er: {
        layoutDirection: 'TB',
        useMaxWidth: true,
        fontSize: 12
      },
      securityLevel: 'loose'
    })
    console.log('Mermaid 初始化成功')
  } catch (error) {
    console.error('Mermaid 初始化失败:', error)
  }
  
  // 添加事件监听器
  document.addEventListener('fullscreenchange', handleFullscreenChange)
  window.addEventListener('resize', handleResize)
  
  // 加载默认模板
  selectedTemplate.value = 'ecommerce'
  loadTemplate()
})

onUnmounted(() => {
  if (parseTimeout) {
    clearTimeout(parseTimeout)
  }
  
  // 清理事件监听器
  document.removeEventListener('fullscreenchange', handleFullscreenChange)
  window.removeEventListener('resize', handleResize)
  document.removeEventListener('mousemove', doResize)
  document.removeEventListener('mouseup', endResize)
})
</script>

<style scoped>
/* 全屏模式样式 */
.fullscreen-mode {
  position: fixed;
  top: 0;
  left: 0;
  width: 100vw;
  height: 100vh;
  z-index: 9999;
  background: white;
}

/* Mermaid 样式优化 */
:deep(.mermaid) {
  display: flex;
  justify-content: center;
  align-items: flex-start;
  min-height: 200px;
}

:deep(.mermaid svg) {
  max-width: 100%;
  height: auto;
  transition: transform 0.3s ease;
}

/* SVG 图表的悬停效果 */
:deep(.mermaid svg .er) {
  transition: all 0.2s ease;
}

:deep(.mermaid svg .er:hover) {
  opacity: 0.8;
}

/* 实体框样式优化 */
:deep(.mermaid svg .entityBox) {
  transition: all 0.3s ease;
}

:deep(.mermaid svg .entityBox:hover) {
  filter: drop-shadow(0 4px 8px rgba(0, 0, 0, 0.1));
}

/* 关系线样式优化 */
:deep(.mermaid svg .relationshipLine) {
  transition: stroke-width 0.2s ease;
}

:deep(.mermaid svg .relationshipLine:hover) {
  stroke-width: 3px;
}

/* 自定义滚动条 */
textarea::-webkit-scrollbar {
  width: 8px;
}

textarea::-webkit-scrollbar-track {
  background: #f1f5f9;
  border-radius: 4px;
}

textarea::-webkit-scrollbar-thumb {
  background: #cbd5e1;
  border-radius: 4px;
  transition: background 0.2s ease;
}

textarea::-webkit-scrollbar-thumb:hover {
  background: #94a3b8;
}

/* 分隔条样式增强 */
.resize-handle {
  position: relative;
  background: linear-gradient(to right, #e2e8f0, #cbd5e1, #e2e8f0);
  transition: all 0.2s ease;
}

.resize-handle::before {
  content: '';
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  width: 2px;
  height: 20px;
  background: #64748b;
  opacity: 0;
  transition: opacity 0.2s ease;
}

.resize-handle:hover::before {
  opacity: 0.5;
}

/* 代码编辑器增强 */
.code-editor {
  font-family: 'JetBrains Mono', 'Fira Code', 'Consolas', monospace;
  line-height: 1.6;
}

.code-editor:focus {
  box-shadow: inset 0 0 0 1px #3b82f6;
}

/* 工具栏按钮悬停效果 */
.toolbar-button {
  position: relative;
  overflow: hidden;
  transition: all 0.3s ease;
}

.toolbar-button::before {
  content: '';
  position: absolute;
  top: 0;
  left: -100%;
  width: 100%;
  height: 100%;
  background: linear-gradient(90deg, transparent, rgba(255, 255, 255, 0.2), transparent);
  transition: left 0.5s ease;
}

.toolbar-button:hover::before {
  left: 100%;
}

/* 弹窗动画 */
.modal-enter-active,
.modal-leave-active {
  transition: all 0.3s ease;
}

.modal-enter-from,
.modal-leave-to {
  opacity: 0;
  transform: scale(0.9);
}

/* 缩放指示器样式 */
.zoom-indicator {
  backdrop-filter: blur(8px);
  border: 1px solid rgba(255, 255, 255, 0.1);
}

/* 快捷键提示样式 */
.shortcut-hint {
  backdrop-filter: blur(8px);
  border: 1px solid rgba(255, 255, 255, 0.1);
  animation: fadeInUp 0.3s ease;
}

@keyframes fadeInUp {
  from {
    opacity: 0;
    transform: translateY(10px);
  }
  to {
    opacity: 1;
    transform: translateY(0);
  }
}

/* 状态栏样式增强 */
.status-bar {
  background: linear-gradient(to right, #f8fafc, #f1f5f9);
  border-top: 1px solid #e2e8f0;
}

/* 加载动画优化 */
.loading-spinner {
  animation: spin 1s linear infinite;
}

@keyframes spin {
  from {
    transform: rotate(0deg);
  }
  to {
    transform: rotate(360deg);
  }
}

/* 语法高亮提示 */
.syntax-hint {
  background: linear-gradient(135deg, #dbeafe, #e0f2fe);
  border: 1px solid #bae6fd;
  box-shadow: 0 2px 4px rgba(59, 130, 246, 0.1);
}

/* 错误状态样式 */
.error-container {
  background: linear-gradient(135deg, #fef2f2, #fee2e2);
  border: 1px solid #fecaca;
  animation: shake 0.5s ease-in-out;
}

@keyframes shake {
  0%, 100% { transform: translateX(0); }
  25% { transform: translateX(-5px); }
  75% { transform: translateX(5px); }
}

/* 响应式布局优化 */
@media (max-width: 1024px) {
  .main-container {
    flex-direction: column;
  }
  
  .left-panel {
    width: 100% !important;
    max-width: 100% !important;
    height: 40vh;
    border-right: none;
    border-bottom: 1px solid #e2e8f0;
  }
  
  .resize-handle {
    display: none;
  }
  
  .right-panel {
    height: 60vh;
  }
}

@media (max-width: 768px) {
  .toolbar {
    flex-wrap: wrap;
    gap: 0.5rem;
  }
  
  .toolbar-button {
    padding: 0.5rem 0.75rem;
    font-size: 0.875rem;
  }
  
  .zoom-controls {
    order: -1;
    width: 100%;
    justify-content: center;
  }
}

/* 性能优化 - 硬件加速 */
.canvas-container,
.mermaid-container {
  transform: translateZ(0);
  will-change: transform;
}

/* 深色主题适配 */
@media (prefers-color-scheme: dark) {
  .bg-gray-50 {
    background-color: #0f172a;
  }
  
  .bg-white {
    background-color: #1e293b;
  }
  
  .text-gray-800 {
    color: #f1f5f9;
  }
  
  .text-gray-600 {
    color: #cbd5e1;
  }
  
  .border-gray-200 {
    border-color: #334155;
  }
  
  .border-gray-300 {
    border-color: #475569;
  }
}

/* 无障碍优化 */
.focus-visible {
  outline: 2px solid #3b82f6;
  outline-offset: 2px;
}

/* 高对比度模式支持 */
@media (prefers-contrast: high) {
  .border {
    border-width: 2px;
  }
  
  .text-gray-500 {
    color: #000;
  }
  
  .bg-gray-50 {
    background-color: #fff;
  }
}

/* 减少动画偏好支持 */
@media (prefers-reduced-motion: reduce) {
  * {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
  }
}

/* 打印样式 */
@media print {
  .toolbar,
  .status-bar,
  .left-panel {
    display: none;
  }
  
  .right-panel {
    width: 100%;
    height: auto;
  }
  
  .mermaid-container {
    transform: none !important;
    page-break-inside: avoid;
  }
}
</style> 